package com.ygqh.baby.controller.mobile;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.foxinmy.weixin4j.exception.WeixinException;
import com.ygqh.baby.ao.AppType;
import com.ygqh.baby.ao.Message;
import com.ygqh.baby.ao.ResponseEntity;
import com.ygqh.baby.constant.Constant;
import com.ygqh.baby.constant.RedisConstant;
import com.ygqh.baby.model.DrawPrize;
import com.ygqh.baby.model.PrizeItem;
import com.ygqh.baby.po.YgDrawPrize;
import com.ygqh.baby.po.YgUser;
import com.ygqh.baby.po.YgUserAddress;
import com.ygqh.baby.redis.RedisDao;
import com.ygqh.baby.service.*;
import com.ygqh.baby.utils.DateConvertUtils;
import com.ygqh.baby.utils.SessionUtil;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @Author: sunshuo
 * @Date: 2019/8/30/030 17:07
 * @Version: 1.0
 */
@Controller
@RequestMapping("/app/drawprize")
public class YgDrawPrizeController extends BaseController {

    @Autowired
    private RedisDao redisDao;
    @Autowired
    private YgDrawPrizeRecordService ygDrawPrizeRecordService;
    @Autowired
    private YgDrawPrizeService ygDrawPrizeService;
    @Autowired
    private WxMpAuthorityService wxMpAuthorityService;
    @Autowired
    private YgUserPrizeService ygUserPrizeService;
    @Autowired
    private YgUserService ygUserService;

    /**
     * 抽奖（方式3：转盘式抽奖）
     *
     * @return
     */
    @RequestMapping(value = "drawPrizeV3", method = RequestMethod.GET)
    @ResponseBody
    public ResponseEntity drawPrizeV3() {
        YgUser user = SessionUtil.getCurrentUser();
        String result = redisDao.get("drawPrizeV3-" + user.getId());
        if (StringUtils.isNotBlank(result)) {
            return ResponseEntity.error("操作频繁，稍后重试", null);
        }
        redisDao.set("drawPrizeV3-" + user.getId(), "1", 5 * 1000);
        ResponseEntity responseEntity = validateDrawPrize();
        if (!responseEntity.isSuccess()) {
            redisDao.del(("drawPrizeV3-" + user.getId()).getBytes());
            return responseEntity;
        }
        DrawPrize drawPrize = (DrawPrize) responseEntity.getData();
        String baseKey = drawPrize.getBaseKey(false, PLATFORM_NO);
        // 验证本次活动赠品数量
        int cashCount = ygDrawPrizeRecordService.
                findCashCountByUserId(null, baseKey, null, null, false);
        if (drawPrize.getGiveCount() != null && cashCount >= drawPrize.getGiveCount()) {
            return ResponseEntity.error("亲，您来晚了，赠品已送完", null);
        }
        Long userId = user.getId();
        // 用户抽奖信息
        YgDrawPrize userDrawPrize = ygDrawPrizeService.findByUserId(userId, baseKey);
        boolean isUseDrawCount = false; // 是否使用用户抽奖信息内的抽奖数
        if (userDrawPrize == null) { // 当前用户未参与过抽奖
            userDrawPrize = ygDrawPrizeService.initDrawPrize(baseKey, userId, 0, 1);
        } else {
            Date date = new Date();
            // 查看当天抽奖记录
            int countByCurrentDate =
                    ygDrawPrizeRecordService.findCashCountByUserId(userId, baseKey, DateConvertUtils.getDateStart(date),
                    DateConvertUtils.getDateEnd(date), false);
            if (countByCurrentDate > 0) { // 当天有过抽奖记录
                isUseDrawCount = true;
                if (userDrawPrize.getCount() <= 0) { // 用户的剩余抽奖次数已用完
                    redisDao.del(("drawPrizeV3-" + user.getId()).getBytes());
                    return ResponseEntity.error("亲，您的次数已用完，赶快去邀请助力吧", null);
                }
            }
        }
        PrizeItem prizeItem = ygDrawPrizeService.drawPrizeV3(drawPrize, user, PLATFORM_NO);
        if (prizeItem == null) {
            redisDao.del(("drawPrizeV3-" + user.getId()).getBytes());
            return ResponseEntity.error("系统异常，请稍后重试或联系客服", null);
        }
        if (isUseDrawCount) {
            userDrawPrize.setCount(userDrawPrize.getCount() - 1);
            ygDrawPrizeService.updateCountById(userDrawPrize.getCount(), userDrawPrize.getId());
        }
        Map<String, Object> data = new HashMap<>(4);
        data.put("index", prizeItem.getIndex());
        data.put("relationCode", prizeItem.getRelationCode());
        data.put("content", prizeItem.getContent());
        data.put("lastCount", userDrawPrize.getCount());
        data.put("type", prizeItem.getType());
        redisDao.del(("drawPrizeV3-" + user.getId()).getBytes());
        return ResponseEntity.success(data);
    }

    /**
     * 获取助力二维码
     *
     * @return
     */
    @RequestMapping("getCodeUrl")
    @ResponseBody
    public ResponseEntity getCodeUrl() {
        YgUser currentUser = SessionUtil.getCurrentUser();
        String result = redisDao.get("getCodeUrl-" + currentUser.getId());
        if (StringUtils.isNotBlank(result)) {
            return ResponseEntity.error("操作频繁，稍后重试", null);
        }
        redisDao.set("getCodeUrl-" + currentUser.getId(), "1", 5 * 1000);
        ResponseEntity responseEntity = validateDrawPrize();
        if (!responseEntity.isSuccess()) {
            redisDao.del(("getCodeUrl-" + currentUser.getId()).getBytes());
            return responseEntity;
        }
        DrawPrize drawPrize = (DrawPrize) responseEntity.getData();
        String baseKey = drawPrize.getBaseKey(false, PLATFORM_NO);
        YgDrawPrize userDrawPrize = ygDrawPrizeService.findByUserId(currentUser.getId(), baseKey);
        if (userDrawPrize == null) {
            userDrawPrize = ygDrawPrizeService.initDrawPrize(baseKey, currentUser.getId(), 0, 1);
        } else if (StringUtils.isNotBlank(userDrawPrize.getQrCode())) {
            return ResponseEntity.success(userDrawPrize.getQrCode());
        }
        String codeUrl;
        try {
            codeUrl = wxMpAuthorityService.findQrCodeUrl("DrawPrize-" + baseKey + "-" + currentUser.getUserName());
        } catch (WeixinException e) {
            logger.error("【转盘抽奖】公众号二维码生成失败，" + e.getMessage(), e);
            redisDao.del(("getCodeUrl-" + currentUser.getId()).getBytes());
            return ResponseEntity.error("生成二维码异常，请稍后再试或联系客服", null);
        }
        YgDrawPrize record = new YgDrawPrize();
        record.setId(userDrawPrize.getId());
        record.setQrCode(codeUrl);
        ygDrawPrizeService.update(record);
        redisDao.del(("getCodeUrl-" + currentUser.getId()).getBytes());
        return ResponseEntity.success(codeUrl);
    }

    @RequestMapping("getCodeUrlByFromCode")
    @ResponseBody
    public ResponseEntity getCodeUrl(@RequestParam String fromCode) {
        ResponseEntity responseEntity = validateDrawPrize();
        if (!responseEntity.isSuccess()) {
            return responseEntity;
        }
        DrawPrize drawPrize = (DrawPrize) responseEntity.getData();
        String baseKey = drawPrize.getBaseKey(false, Constant.YIIGOO_PLATFORM_NO);
        YgUser fromUser = ygUserService.findBySourceCode(fromCode);
        if (fromUser == null) {
            logger.error("【转盘抽奖】邀请助力链接source异常，fromCode={}", fromCode);
            return ResponseEntity.error("系统异常，请请稍后再试或联系客服", null);
        }
        YgDrawPrize userDrawPrize = ygDrawPrizeService.findByUserId(fromUser.getId(), baseKey);
        if (userDrawPrize == null) {
            logger.error("【转盘抽奖】邀请助力链接source异常，fromCode={}", fromCode);
            return ResponseEntity.error("系统异常，请请稍后再试或联系客服", null);
        }
        if (StringUtils.isNotBlank(userDrawPrize.getQrCode())) {
            return ResponseEntity.success(userDrawPrize.getQrCode());
        }
        String codeUrl;
        try {
            codeUrl = wxMpAuthorityService.findQrCodeUrl("DrawPrize-" + baseKey + "-" + fromCode);
        } catch (WeixinException e) {
            logger.error("【转盘抽奖】公众号二维码生成失败，" + e.getMessage(), e);
            return ResponseEntity.error("生成二维码异常，请稍后再试或联系客服", null);
        }
        YgDrawPrize record = new YgDrawPrize();
        record.setId(userDrawPrize.getId());
        record.setQrCode(codeUrl);
        ygDrawPrizeService.update(record);
        return ResponseEntity.success(codeUrl);
    }

    /**
     * 获取抽奖次数
     *
     * @return
     */
    @RequestMapping(value = "/getDrawPrizeCountV3")
    @ResponseBody
    public ResponseEntity getDrawPrizeCountV3() {
        YgUser user = SessionUtil.getCurrentUser();
        String result = redisDao.get("getDrawPrizeCountV3-" + user.getId());
        if (StringUtils.isNotBlank(result)) {
            return ResponseEntity.error("操作频繁，稍后重试", null);
        }
        redisDao.set("getDrawPrizeCountV3-" + user.getId(), "1", 5 * 1000);
        ResponseEntity responseEntity = validateDrawPrize();
        if (!responseEntity.isSuccess()) {
            redisDao.del(("getDrawPrizeCountV3-" + user.getId()).getBytes());
            return responseEntity;
        }
        DrawPrize drawPrize = (DrawPrize) responseEntity.getData();
        String baseKey = drawPrize.getBaseKey(false, PLATFORM_NO);
        Long userId = user.getId();
        // 用户抽奖信息
        int currentDateCount = 1;
        YgDrawPrize userDrawPrize = ygDrawPrizeService.findByUserId(userId, baseKey);
        if (userDrawPrize == null) { // 当前用户未参与过抽奖
            userDrawPrize = ygDrawPrizeService.initDrawPrize(baseKey, userId, 0, 1);
        } else {
            Date date = new Date();
            // 查看当天抽奖记录
            int countByCurrentDate = ygDrawPrizeRecordService.findCashCountByUserId(userId, baseKey, DateConvertUtils.getDateStart(date),
                    DateConvertUtils.getDateEnd(date), false);
            if (countByCurrentDate > 0) { // 当天有过抽奖记录
                currentDateCount--;
            }
        }
        redisDao.del(("getDrawPrizeCountV3-" + user.getId()).getBytes());
        return ResponseEntity.success(userDrawPrize.getCount() + currentDateCount);
    }

    /**
     * 兑换实物奖品
     *
     * @param skuId skuId
     * @param addrInfo 收货地址信息
     * @return
     */
    @RequestMapping(value = "/cashGoodsPrizeV3")
    @ResponseBody
    public ResponseEntity cashGoodsPrizeV3(@RequestParam Long skuId, @RequestParam String addrInfo,
                                           @RequestParam(defaultValue = "Small") AppType appType) {
        YgUser user = SessionUtil.getCurrentUser();
        String result = redisDao.get("cashGoodsPrizeV3-" + user.getId());
        if (StringUtils.isNotBlank(result)) {
            return ResponseEntity.error("操作频繁，稍后重试", null);
        }
        redisDao.set("cashGoodsPrizeV3-" + user.getId(), "1", 5 * 1000);
        ResponseEntity responseEntity = validateDrawPrize();
        if (!responseEntity.isSuccess()) {
            redisDao.del(("cashGoodsPrizeV3-" + user.getId()).getBytes());
            return responseEntity;
        }
        DrawPrize drawPrize = (DrawPrize) responseEntity.getData();
        String baseKey = drawPrize.getBaseKey(false, PLATFORM_NO);
        YgUserAddress address = JSON.parseObject(addrInfo, new TypeReference<YgUserAddress>() {
        });
        if (address == null) {
            logger.error("【转盘抽奖】前端传递的地址信息异常，addrInfo={}", addrInfo);
            redisDao.del(("cashGoodsPrizeV3-" + user.getId()).getBytes());
            return ResponseEntity.error("地址信息异常，请稍后再试或联系客服", null);
        }
        address.setUserId(user.getId());
        Message message = ygUserPrizeService.cashPrize(skuId, baseKey, address, PLATFORM_NO, appType);
        redisDao.del(("cashGoodsPrizeV3-" + user.getId()).getBytes());
        return ResponseEntity.converter(message);
    }

    private ResponseEntity validateDrawPrize() {
        String res = redisDao.get(RedisConstant.PRIZE_ITEM_KEY);
        if (StringUtils.isBlank(res)) {
            return ResponseEntity.error("活动已结束", null);
        }
        // 解析抽奖活动信息
        DrawPrize drawPrize = JSON.parseObject(res, DrawPrize.class);
        if (!drawPrize.isValid()) {
            return ResponseEntity.error("活动已结束", null);
        }
        return ResponseEntity.success(drawPrize);
    }
}
